feat(docs): expand ComponentGrid in llms.txt output#1509
feat(docs): expand ComponentGrid in llms.txt output#1509
Conversation
Add a rule that transforms <ComponentGrid /> into a categorized markdown list of components so /llms/docs/components.txt exposes the full component index instead of a bare MDX tag. Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
|
|
Note Reviews pausedIt looks like this branch is under active development. To avoid overwhelming you with review comments due to an influx of new commits, CodeRabbit has automatically paused this review. You can configure this behavior by changing the Use the following commands to manage reviews:
Use the checkboxes below for quick actions:
📝 WalkthroughWalkthrough로컬 컴포넌트 MDX 문서를 스캔해 frontmatter로 엔트리를 수집·캐시하고, 카테고리별로 그룹화한 Markdown 링크 목록을 생성해 Changes
Sequence Diagram(s)sequenceDiagram
participant LLM as "LLM Processor"
participant Rule as "ComponentGrid Rule"
participant FS as "Filesystem (docs/components)"
participant Cache as "In‑memory Cache"
LLM->>Rule: encounters <ComponentGrid /> node
Rule->>Cache: check cached entries
alt cache miss
Rule->>FS: scan category folders & read .mdx files
FS-->>Rule: return file list & frontmatter
Rule->>Rule: parse frontmatter, filter deprecated, build entries
Rule->>Cache: store entries
end
Rule->>Rule: buildMarkdown(grouped entries)
Rule-->>LLM: return HTML node with generated markdown
Estimated code review effort🎯 3 (Moderate) | ⏱️ ~20 minutes Poem
🚥 Pre-merge checks | ✅ 4 | ❌ 1❌ Failed checks (1 warning)
✅ Passed checks (4 passed)
✏️ Tip: You can configure your own custom pre-merge checks in the settings. ✨ Finishing Touches🧪 Generate unit tests (beta)
Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out. Comment |
There was a problem hiding this comment.
Actionable comments posted: 2
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.
Inline comments:
In `@docs/app/_llms/rules/component-grid-rule.test.ts`:
- Around line 5-30: The tests in component-grid-rule.test.ts use partial
matching (toContain/not.toContain) against normalizeLLMBodyWithRules output;
replace these with full-fixture comparisons using normalizeForAssert and
readFixture: import { normalizeForAssert, readFixture } from
'docs/app/_llms/test-utils.ts', call const expected =
readFixture('<appropriate-fixture-filename>.md') and assert
expect(normalizeForAssert(actual)).toBe(normalizeForAssert(expected)); update
each test ("expands ComponentGrid...", "excludes deprecated components...") to
use this pattern and corresponding fixtures, and rename the third test from
"leaves the node as-is when no components are available" to "non-target node
passthrough" (or similar) while also asserting full-fixture equality for the
passthrough case using normalizeForAssert. Ensure tests still call
normalizeLLMBodyWithRules(input, [componentGridRule]) as before.
In `@docs/app/_llms/rules/component-grid-rule.ts`:
- Around line 28-42: parseFrontmatter currently returns all frontmatter values
as strings so a frontmatter like deprecated: false becomes the string "false"
and is treated truthily; update parseFrontmatter to detect boolean-like values
(at least for the "deprecated" key) and convert "true"/"false"
(case-insensitive) to actual booleans (true/false) before storing in result, or
more generally parse "true"/"false" and numeric strings to proper types;
reference the parseFrontmatter function and the "deprecated" frontmatter key so
the boolean false is not treated as truthy in the downstream filter that
excludes deprecated components.
🪄 Autofix (Beta)
Fix all unresolved CodeRabbit comments on this PR:
- Push a commit to this branch (recommended)
- Create a new PR with the fixes
ℹ️ Review info
⚙️ Run configuration
Configuration used: Path: .coderabbit.yaml
Review profile: CHILL
Plan: Pro
Run ID: 7cfa20d2-5930-43f0-ab0e-243cd406575d
📒 Files selected for processing (3)
docs/app/_llms/rules/component-grid-rule.test.tsdocs/app/_llms/rules/component-grid-rule.tsdocs/app/_llms/rules/index.ts
Alpha Preview (Docs)
|
- Treat deprecated: false / "no" / empty as not deprecated so valid components are no longer filtered out by the string-coerced parser. - Switch tests to fixture-based equality via readFixture / normalizeForAssert to match the project's _llms test convention, and add unit coverage for isDeprecatedValue. Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
Alpha Preview (Stackflow SPA)
|
Alpha Preview (Storybook)
|
There was a problem hiding this comment.
🧹 Nitpick comments (4)
docs/app/_llms/rules/component-grid-rule.ts (4)
86-91: 모듈 수준 캐시는 프로세스 생애 동안 무효화되지 않습니다.
cachedEntries가 첫 호출 이후 영구히 재사용되므로, dev 서버가 장시간 떠 있는 상태에서 컴포넌트 MDX를 추가/수정/삭제해도/llms/docs/components.txt결과에 반영되지 않습니다. 빌드 타임에만 실행된다면 문제없지만, HMR/런타임 호출 경로가 있다면NODE_ENV !== 'production'에서 캐시를 우회하거나 파일 mtime 기반 무효화를 고려해 주세요.🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed. In `@docs/app/_llms/rules/component-grid-rule.ts` around lines 86 - 91, The module-level cache (cachedEntries) never invalidates, so getEntries() will return stale ComponentEntry[] after files change; update getEntries() to invalidate or bypass the cache when NODE_ENV !== 'production' (or when file mtimes change): e.g., check process.env.NODE_ENV and call loadEntries() directly in dev, or track last-modified timestamps of the source MDX files and refresh cachedEntries when any mtime is newer; target symbols: cachedEntries, getEntries, and loadEntries.
50-52:titleCase는 첫 글자만 대문자화합니다.
(form-controls)같은 다단어/하이픈 카테고리 폴더가 생기면"Form-controls"처럼 어색하게 출력됩니다. 현재 카테고리 폴더 네이밍 컨벤션이 단일 소문자 단어로 고정되어 있다면 문제 없지만, 향후 확장을 고려해 단어 경계별 대문자화(또는 하이픈/언더스코어 처리)를 권장합니다.♻️ 예시
-function titleCase(value: string): string { - return value.charAt(0).toUpperCase() + value.slice(1); -} +function titleCase(value: string): string { + return value + .split(/[-_\s]+/) + .filter(Boolean) + .map((word) => word.charAt(0).toUpperCase() + word.slice(1)) + .join(" "); +}🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed. In `@docs/app/_llms/rules/component-grid-rule.ts` around lines 50 - 52, titleCase currently only uppercases the first character and yields awkward results for multi-word or hyphenated names; update the titleCase function to split the input on hyphens, underscores or spaces (e.g. using a regex like /[-_\s]+/), capitalize the first letter of each segment and lowercase the rest, then join the segments with a space so inputs like "form-controls" or "multi_word name" become "Form Controls" (handle empty segments safely).
108-111: description 내 특수문자로 마크다운이 깨질 수 있습니다.프론트매터
description에],), 개행, 백틱 등이 포함되면- [title](url) — description라인이 깨집니다. 프론트매터 파싱 단계에서 따옴표는 이미 벗겨지므로, 렌더 시점에 최소한]/)/개행 정도는 이스케이프하거나 치환하는 것을 권장합니다.🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed. In `@docs/app/_llms/rules/component-grid-rule.ts` around lines 108 - 111, description에 포함된 특수문자 때문에 마크다운이 깨집니다; for (const entry of list) 루프에서 suffix를 만들기 전에 entry.description을 안전하게 치환/이스케이프하세요 (예: ']' → '\]', ')' → '\)', 줄바꿈은 공백 또는 '\\n'으로 대체, 백틱은 '\`'로 이스케이프 등). 그런 다음 lines.push(`- [${entry.title}](${entry.url})${suffix}`)에서 치환된 safeDescription을 사용하도록 변경하세요.
33-48:parseFrontmatter유틸리티는 프론트매터 파싱 개선으로 이점을 볼 수 있습니다.현재 정규식
/^["']|["']$/g는 비대칭 입력(예:title: 'Hello")을 예기치 않게 처리하며, 프로젝트에 이미 있는yaml@^2.8.2라이브러리를 사용하면 더 견고하게 만들 수 있습니다. 실제 문서의 프론트매터는 따옴표 없는 단순 key-value 형식(title: Docs MCP,description: ...)이므로 현재 동작에 즉각적인 문제는 없지만, 더 견고한 파싱을 위해 yaml 패키지 활용을 검토할 수 있습니다.참고로,
componentGridRule의 Rule 인터페이스 구현(이름, match, transform)은 적절하게 분리되어 있고, 에러 처리도 안전하게 원본 노드를 반환하고 있습니다.🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed. In `@docs/app/_llms/rules/component-grid-rule.ts` around lines 33 - 48, Replace the fragile manual frontmatter parsing in parseFrontmatter with the project's yaml library: keep the existing frontmatter extraction (the regex that finds the --- block) but pass match[1] to YAML.parse (imported from the yaml@^2.8.2 package) to obtain a parsed object, then convert/normalize its values to strings (e.g., String(value)) before returning a Record<string,string>; catch and return {} on parse errors so behavior remains safe. Ensure you update the parseFrontmatter function to import YAML and to handle non-string YAML values and exceptions.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.
Nitpick comments:
In `@docs/app/_llms/rules/component-grid-rule.ts`:
- Around line 86-91: The module-level cache (cachedEntries) never invalidates,
so getEntries() will return stale ComponentEntry[] after files change; update
getEntries() to invalidate or bypass the cache when NODE_ENV !== 'production'
(or when file mtimes change): e.g., check process.env.NODE_ENV and call
loadEntries() directly in dev, or track last-modified timestamps of the source
MDX files and refresh cachedEntries when any mtime is newer; target symbols:
cachedEntries, getEntries, and loadEntries.
- Around line 50-52: titleCase currently only uppercases the first character and
yields awkward results for multi-word or hyphenated names; update the titleCase
function to split the input on hyphens, underscores or spaces (e.g. using a
regex like /[-_\s]+/), capitalize the first letter of each segment and lowercase
the rest, then join the segments with a space so inputs like "form-controls" or
"multi_word name" become "Form Controls" (handle empty segments safely).
- Around line 108-111: description에 포함된 특수문자 때문에 마크다운이 깨집니다; for (const entry of
list) 루프에서 suffix를 만들기 전에 entry.description을 안전하게 치환/이스케이프하세요 (예: ']' → '\]',
')' → '\)', 줄바꿈은 공백 또는 '\\n'으로 대체, 백틱은 '\`'로 이스케이프 등). 그런 다음 lines.push(`-
[${entry.title}](${entry.url})${suffix}`)에서 치환된 safeDescription을 사용하도록 변경하세요.
- Around line 33-48: Replace the fragile manual frontmatter parsing in
parseFrontmatter with the project's yaml library: keep the existing frontmatter
extraction (the regex that finds the --- block) but pass match[1] to YAML.parse
(imported from the yaml@^2.8.2 package) to obtain a parsed object, then
convert/normalize its values to strings (e.g., String(value)) before returning a
Record<string,string>; catch and return {} on parse errors so behavior remains
safe. Ensure you update the parseFrontmatter function to import YAML and to
handle non-string YAML values and exceptions.
ℹ️ Review info
⚙️ Run configuration
Configuration used: Path: .coderabbit.yaml
Review profile: CHILL
Plan: Pro
Run ID: 63621421-39bf-49d6-b860-49914712fd80
📒 Files selected for processing (5)
docs/app/_llms/__fixtures__/component-grid/basic.output.mddocs/app/_llms/__fixtures__/component-grid/passthrough.input.mdxdocs/app/_llms/__fixtures__/component-grid/passthrough.output.mdxdocs/app/_llms/rules/component-grid-rule.test.tsdocs/app/_llms/rules/component-grid-rule.ts
✅ Files skipped from review due to trivial changes (3)
- docs/app/_llms/fixtures/component-grid/passthrough.output.mdx
- docs/app/_llms/fixtures/component-grid/passthrough.input.mdx
- docs/app/_llms/fixtures/component-grid/basic.output.md
🚧 Files skipped from review as they are similar to previous changes (1)
- docs/app/_llms/rules/component-grid-rule.test.ts
Replace hardcoded /llms/docs/components/{slug}.txt template with the
existing getLLMMarkdownUrl helper so URL construction stays centralized.
Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
There was a problem hiding this comment.
♻️ Duplicate comments (1)
docs/app/_llms/rules/component-grid-rule.ts (1)
16-21:⚠️ Potential issue | 🟡 Minor
deprecated판정은 true 계열 allowlist로 좁히는 편이 안전합니다.현재는 빈 값/
false/no만 제외해서deprecated: off나deprecated: 0같은 false 계열 값도 deprecated로 처리되어 컴포넌트 인덱스에서 빠질 수 있습니다. 명시적인 true 계열만 제외하도록 좁혀 주세요.🐛 제안 수정
export function isDeprecatedValue(value: string | undefined): boolean { if (value === undefined) return false; const normalized = value.trim().toLowerCase(); if (normalized === "") return false; - return normalized !== "false" && normalized !== "no"; + return normalized === "true" || normalized === "yes" || normalized === "on" || normalized === "1"; }🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed. In `@docs/app/_llms/rules/component-grid-rule.ts` around lines 16 - 21, The isDeprecatedValue function currently treats any value other than empty/"false"/"no" as deprecated, which mislabels values like "off" or "0"; update isDeprecatedValue to return true only for an explicit true allowlist (e.g., "true","yes","1","on") and false for all other values (still returning false for undefined/empty). Modify the logic inside isDeprecatedValue to normalize the input and check membership in that explicit true-set instead of using the current negative checks.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.
Duplicate comments:
In `@docs/app/_llms/rules/component-grid-rule.ts`:
- Around line 16-21: The isDeprecatedValue function currently treats any value
other than empty/"false"/"no" as deprecated, which mislabels values like "off"
or "0"; update isDeprecatedValue to return true only for an explicit true
allowlist (e.g., "true","yes","1","on") and false for all other values (still
returning false for undefined/empty). Modify the logic inside isDeprecatedValue
to normalize the input and check membership in that explicit true-set instead of
using the current negative checks.
ℹ️ Review info
⚙️ Run configuration
Configuration used: Path: .coderabbit.yaml
Review profile: CHILL
Plan: Pro
Run ID: ff14e8c9-dadf-42fa-924b-5b15a4344355
📒 Files selected for processing (1)
docs/app/_llms/rules/component-grid-rule.ts
| return null; | ||
| } | ||
|
|
||
| function parseFrontmatter(source: string): Record<string, string> { |
Replace the ad-hoc regex parser and string-based isDeprecatedValue helper with gray-matter, consistent with generate-docs-index. Boolean frontmatter values are now parsed as real booleans. Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
There was a problem hiding this comment.
Actionable comments posted: 1
🧹 Nitpick comments (2)
docs/app/_llms/rules/component-grid-rule.ts (2)
70-75: 프로세스 수명 동안 유지되는 캐시로 인한 개발 중 stale 위험.
cachedEntries는 모듈 수준에서 한 번만 채워지고 무효화 수단이 없습니다. 빌드 타임 일회성 실행에서는 문제가 없지만, 같은 프로세스에서 dev 서버가 장시간 유지되는 경우 새로 추가/수정한 컴포넌트 MDX가 반영되지 않습니다.Rule인터페이스에 reset 훅이 없는 점을 감안할 때, 최소한NODE_ENV !== "production"일 때는 캐시를 건너뛰는 것을 고려해 보세요.♻️ 제안 수정
function getEntries(): ComponentEntry[] { + if (process.env.NODE_ENV !== "production") return loadEntries(); if (cachedEntries === null) cachedEntries = loadEntries(); return cachedEntries; }🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed. In `@docs/app/_llms/rules/component-grid-rule.ts` around lines 70 - 75, The module-level cachedEntries causes stale data in long-lived dev processes; update getEntries to bypass or not persist the cache when not in production by checking process.env.NODE_ENV !== "production" and, in that case, always call loadEntries() (or return a fresh load) instead of returning cachedEntries; keep using cachedEntries only when NODE_ENV === "production" so loadEntries() is still cached in production. Ensure you reference and modify cachedEntries, getEntries, and loadEntries accordingly.
34-36:titleCase가 다중 단어 카테고리를 제대로 처리하지 못합니다.
(data-display)나(form-controls)같은 하이픈/언더스코어 카테고리 폴더명이 오면Data-display처럼 첫 글자만 대문자가 되어 결과물 가독성이 떨어집니다. 단어 구분자 단위로 타이틀 케이스를 적용하는 방식을 고려해 주세요.♻️ 제안 수정
function titleCase(value: string): string { - return value.charAt(0).toUpperCase() + value.slice(1); + return value + .split(/[-_\s]+/) + .map((w) => (w ? w.charAt(0).toUpperCase() + w.slice(1) : w)) + .join(" "); }🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed. In `@docs/app/_llms/rules/component-grid-rule.ts` around lines 34 - 36, titleCase 함수가 하이픈/언더스코어가 포함된 다중 단어 카테고리를 제대로 처리하지 못하므로, titleCase 구현을 변경해 단어 구분자(/[-_\s]+/)로 문자열을 분리한 뒤 각 토큰의 첫 글자만 대문자로 나머지는 소문자로 변환하고 공백으로 연결하여 반환하도록 수정하세요; 대상 심볼: function titleCase(value: string): string, 업데이트 시 입력에 빈값이 들어올 경우 기존 동작(빈 문자열 반환)을 유지하도록 처리하세요.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.
Inline comments:
In `@docs/app/_llms/rules/component-grid-rule.ts`:
- Around line 23-32: resolveComponentsDir currently returns null silently which
causes loadEntries to return an empty array and transform to leave the original
<ComponentGrid /> node unchanged; add a visible warning when the components
directory cannot be found so CI/builds can catch it. Specifically, update
resolveComponentsDir (or immediately after its return in loadEntries) to emit a
warning via the project's logging facility (e.g., processLogger.warn or
console.warn if no logger is available) that includes the attempted candidate
paths and the fact that component entries were not loaded; ensure the warning is
produced before transform runs so the missing directory is recorded during CI.
---
Nitpick comments:
In `@docs/app/_llms/rules/component-grid-rule.ts`:
- Around line 70-75: The module-level cachedEntries causes stale data in
long-lived dev processes; update getEntries to bypass or not persist the cache
when not in production by checking process.env.NODE_ENV !== "production" and, in
that case, always call loadEntries() (or return a fresh load) instead of
returning cachedEntries; keep using cachedEntries only when NODE_ENV ===
"production" so loadEntries() is still cached in production. Ensure you
reference and modify cachedEntries, getEntries, and loadEntries accordingly.
- Around line 34-36: titleCase 함수가 하이픈/언더스코어가 포함된 다중 단어 카테고리를 제대로 처리하지 못하므로,
titleCase 구현을 변경해 단어 구분자(/[-_\s]+/)로 문자열을 분리한 뒤 각 토큰의 첫 글자만 대문자로 나머지는 소문자로 변환하고
공백으로 연결하여 반환하도록 수정하세요; 대상 심볼: function titleCase(value: string): string, 업데이트 시
입력에 빈값이 들어올 경우 기존 동작(빈 문자열 반환)을 유지하도록 처리하세요.
🪄 Autofix (Beta)
Fix all unresolved CodeRabbit comments on this PR:
- Push a commit to this branch (recommended)
- Create a new PR with the fixes
ℹ️ Review info
⚙️ Run configuration
Configuration used: Path: .coderabbit.yaml
Review profile: CHILL
Plan: Pro
Run ID: fa5d33b9-8c03-452d-b048-427f55dfd6f3
📒 Files selected for processing (3)
docs/app/_llms/rules/component-grid-rule.test.tsdocs/app/_llms/rules/component-grid-rule.tsdocs/app/_llms/rules/index.ts
✅ Files skipped from review due to trivial changes (1)
- docs/app/_llms/rules/index.ts
🚧 Files skipped from review as they are similar to previous changes (1)
- docs/app/_llms/rules/component-grid-rule.test.ts
Silently returning null masked the original symptom this PR fixes — the <ComponentGrid /> MDX tag leaking into llms.txt output. Log the attempted candidate paths so CI/builds can surface the failure. Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
There was a problem hiding this comment.
Actionable comments posted: 1
🧹 Nitpick comments (3)
docs/app/_llms/rules/component-grid-rule.ts (3)
52-55: 디렉터리 엔트리를 파일로 오인할 수 있습니다.
fs.readdirSync(categoryDir)는 파일/디렉터리 구분 없이 이름 목록을 반환합니다. 카테고리 하위에.mdx로 끝나는 디렉터리가 우연히 존재하면 Line 55의fs.readFileSync가EISDIR을 던지고, 바깥transform의catch로 전파되어 전체 컴포넌트 그리드가 조용히 원본 MDX 노드로 폴백됩니다. 현재 구조상 발생 가능성은 낮지만, 상위readdirSync와 동일하게withFileTypes로 필터링하는 편이 일관성·안전성 면에서 낫습니다.♻️ 제안 수정
- for (const file of fs.readdirSync(categoryDir)) { - if (!file.endsWith(".mdx")) continue; + for (const entry of fs.readdirSync(categoryDir, { withFileTypes: true })) { + if (!entry.isFile() || !entry.name.endsWith(".mdx")) continue; + const file = entry.name;🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed. In `@docs/app/_llms/rules/component-grid-rule.ts` around lines 52 - 55, The code treats entries from fs.readdirSync(categoryDir) as files and may call fs.readFileSync on directories; change the loop that iterates categoryDir entries (in component-grid-rule.ts) to call fs.readdirSync(categoryDir, { withFileTypes: true }) and filter Dirent objects by dirent.isFile() && dirent.name.endsWith('.mdx') before calling fs.readFileSync on path.join(categoryDir, dirent.name); this mirrors the earlier use of withFileTypes and prevents EISDIR when a directory name ends with .mdx.
71-76: 모듈 수준 캐시가 영구히 유지됩니다.
cachedEntries는 프로세스 수명 동안 무효화되지 않습니다. 빌드 시점 1회 실행이라면 무해하지만,next dev나 watch 환경에서 동일 프로세스가 재사용되는 경우 새로 추가/삭제된 컴포넌트 문서가 반영되지 않습니다. 파일 시스템 변경이 빈번한 개발 환경을 지원해야 한다면 mtime 기반 재검증이나 개발 모드에서만 캐시를 비활성화하는 방안을 고려해 주세요. (현재 사용 맥락이 빌드 전용이라면 무시하셔도 됩니다.)🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed. In `@docs/app/_llms/rules/component-grid-rule.ts` around lines 71 - 76, The module-level cache cachedEntries (used by getEntries and populated via loadEntries) is never invalidated, so additions/deletions during a long-lived process (eg. next dev/watch) won't be picked up; change getEntries to either skip caching in development (check NODE_ENV or a dev flag) or add revalidation logic (compare directory/file mtimes or a timestamp and call loadEntries again when sources changed) so loadEntries is re-run when filesystem changes are detected; ensure cachedEntries is updated/cleared after revalidation.
110-110:html노드로 Markdown 문자열을 주입하는 방식 재고.현재
buildMarkdown()이 생성한 Markdown 문자열(## …,- […](url))을type: "html"노드로 삽입합니다. 최종 직렬화기가mdast-util-to-markdown이면html노드는 그대로 통과되어 결과물에서는 Markdown으로 보이지만, 의미상으론 AST가 HTML로 태그되어 있어 downstream에서 heading/list 노드를 순회하는 다른 룰/플러그인이 이 섹션을 건너뛰게 됩니다. 가능하다면heading/list/listItem/link/text등 mdast 노드를 직접 조립해 반환하는 편이 파이프라인 확장성에 유리합니다.As per coding guidelines: "Prioritize AST transformation over string regex post-processing".
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed. In `@docs/app/_llms/rules/component-grid-rule.ts` at line 110, The code currently injects a Markdown string via a node like `return [{ type: "html", value: buildMarkdown(entries) }];` which treats the content as HTML and breaks downstream AST traversal; instead modify the implementation so you assemble and return mdast nodes directly (e.g., create `heading`, `list`, `listItem`, `link`, `text` nodes) rather than a single `html` node. Update `buildMarkdown` (or create a new helper called by the rule) to output an array of mdast node objects (heading/list/listItem/link/text) and change the return to return that array of nodes so other rules/plugins can traverse semantic AST nodes. Ensure node shapes follow mdast conventions (type and children/position/identifier where applicable).
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.
Inline comments:
In `@docs/app/_llms/rules/component-grid-rule.ts`:
- Around line 106-114: The transform() catch block currently swallows errors
from getEntries()/buildMarkdown() silently; change it to catch the thrown error
(catch (err)) and emit a warning log containing context ("ComponentGrid
transform failed" or similar) plus the error details before returning [node],
using the project's existing logger (e.g., processLogger.warn) or console.warn
if no logger is in scope; keep the safe fallback to return the original node but
ensure CI/builds can detect the problem via the logged warning.
---
Nitpick comments:
In `@docs/app/_llms/rules/component-grid-rule.ts`:
- Around line 52-55: The code treats entries from fs.readdirSync(categoryDir) as
files and may call fs.readFileSync on directories; change the loop that iterates
categoryDir entries (in component-grid-rule.ts) to call
fs.readdirSync(categoryDir, { withFileTypes: true }) and filter Dirent objects
by dirent.isFile() && dirent.name.endsWith('.mdx') before calling
fs.readFileSync on path.join(categoryDir, dirent.name); this mirrors the earlier
use of withFileTypes and prevents EISDIR when a directory name ends with .mdx.
- Around line 71-76: The module-level cache cachedEntries (used by getEntries
and populated via loadEntries) is never invalidated, so additions/deletions
during a long-lived process (eg. next dev/watch) won't be picked up; change
getEntries to either skip caching in development (check NODE_ENV or a dev flag)
or add revalidation logic (compare directory/file mtimes or a timestamp and call
loadEntries again when sources changed) so loadEntries is re-run when filesystem
changes are detected; ensure cachedEntries is updated/cleared after
revalidation.
- Line 110: The code currently injects a Markdown string via a node like `return
[{ type: "html", value: buildMarkdown(entries) }];` which treats the content as
HTML and breaks downstream AST traversal; instead modify the implementation so
you assemble and return mdast nodes directly (e.g., create `heading`, `list`,
`listItem`, `link`, `text` nodes) rather than a single `html` node. Update
`buildMarkdown` (or create a new helper called by the rule) to output an array
of mdast node objects (heading/list/listItem/link/text) and change the return to
return that array of nodes so other rules/plugins can traverse semantic AST
nodes. Ensure node shapes follow mdast conventions (type and
children/position/identifier where applicable).
🪄 Autofix (Beta)
Fix all unresolved CodeRabbit comments on this PR:
- Push a commit to this branch (recommended)
- Create a new PR with the fixes
ℹ️ Review info
⚙️ Run configuration
Configuration used: Path: .coderabbit.yaml
Review profile: CHILL
Plan: Pro
Run ID: aa8bc0e1-bcdf-4e31-8493-a793590d77fb
📒 Files selected for processing (1)
docs/app/_llms/rules/component-grid-rule.ts
Mirror the resolveComponentsDir warning: surfacing the fallback so a failing getEntries/buildMarkdown can be caught in CI instead of silently leaving the <ComponentGrid /> tag in llms.txt output. Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
Add a rule that transforms into a categorized markdown list of components so /llms/docs/components.txt exposes the full component index instead of a bare MDX tag.
Summary by CodeRabbit
릴리스 노트
새로운 기능
테스트